
/* Generated by Interface Builder */

#import "StellaView.h"
#import <appkit/appkit.h>
#import <dpsclient/dpsclient.h>

void RunStellaEntry(DPSTimedEntry te, double timeNow, void *data)
{
  /* we set data to self so we can call this method from the timed entry */
	[(StellaView *)data display];
}

@implementation StellaView

- showStar :(int)x :(int)y :(int)cycle
{
	NXImage *myImage = NULL;
	NXPoint myPoint;

	switch(cycle)
	{
		case 0	:	myImage = [NXImage findImageNamed:"Stella1"];break;
		case 1	:	myImage = [NXImage findImageNamed:"Stella2"];break;
		case 2	:	myImage = [NXImage findImageNamed:"Stella3"];break;
		case 3	:	myImage = [NXImage findImageNamed:"Stella4"];break;
		case 4	:	myImage = [NXImage findImageNamed:"Stella5"];break;
		case 5	:	myImage = [NXImage findImageNamed:"Stella6"];break;
		case 6	:	myImage = [NXImage findImageNamed:"Stella7"];break;
	}

	myPoint.x = x*STAR_WIDTH;
	myPoint.y = y*STAR_HEIGHT;
	[myImage composite:NX_COPY toPoint:&myPoint];

	return self;
}

- deleteStar :(int)x :(int)y
{
	NXRect myRect;

	PSsetgray(0.0);

	myRect.origin.x = x*STAR_WIDTH;
	myRect.origin.y = y*STAR_HEIGHT;
	myRect.size.width = STAR_WIDTH;
	myRect.size.height = STAR_HEIGHT;

	NXRectFill(&myRect);

	return self;
}

- drawSelf:(const NXRect *)rects :(int)rectCount;
{
	int count;

	if(!flags.blankedscreen)
	{
		PSsetgray(0.0);
		NXRectFill(&bounds);
		flags.blankedscreen = TRUE;
	}

	// Show all the stars
	for(count = 0; count < NUMBER_STARS; count++)
		[self showStar :stars[count].x :stars[count].y :stars[count].cycle];

	for(count = 0; count < NUMBER_STARS; count++)
	{
		if(!stars[count].forward)
			stars[count].cycle--;
		else
			stars[count].cycle++;

		if(stars[count].cycle == stars[count].magnitude)
			stars[count].forward = !stars[count].forward;

		if(stars[count].cycle == -1)
		{
			[self deleteStar :stars[count].x :stars[count].y];
			[self makeMyStar:count];
		}
	}

	return self;
}

- startAnimation
{
	myTimedEntry =
		DPSAddTimedEntry((float)0.1,
			&RunStellaEntry,self,NX_BASETHRESHOLD);

	return self;
}

- endAnimation
{
	DPSRemoveTimedEntry(myTimedEntry);

	return self;
}

- initFrame:(const NXRect *)frameRect
{
	int count;

	[super initFrame :frameRect];

	flags.blankedscreen = FALSE;

	width = frameRect->size.width/STAR_WIDTH;
	height = frameRect->size.height/STAR_HEIGHT;

	for(count = 0; count < NUMBER_STARS; count++)
		stars[count].magnitude = 0;

	for(count = 0; count < NUMBER_STARS; count++)
	{
		[self makeMyStar :count];
		stars[count].cycle = random()%stars[count].magnitude;
		stars[count].forward = random()%2;
	}

	return self;
}

- (BOOL)starExists :(int)x :(int)y
{
	int count;

	for(count = 0; count < NUMBER_STARS; count++)
		if((stars[count].magnitude) && (stars[count].x == x) &&
		   (stars[count].y == y))
			return TRUE;

	return FALSE;
}

- makeMyStar :(int)number
{
	int x,y;

	do
	{
		x = random()%width;
		y = random()%height;
	}
	while([self starExists :x :y]);

	stars[number].x = x;
	stars[number].y = y;

	stars[number].cycle = 0;
	stars[number].magnitude = random()%(MAX_MAGNITUDE-1)+1;
	stars[number].forward = TRUE;

	return self;
}

@end
